package com.gavin.plugin.database.ext;

import java.util.Random;

import com.gavin.model.Model;
import com.gavin.plugin.database.help.ValueUtils;

public class MathExt {

	private static Random random = new Random(System.currentTimeMillis());
	
	public static long getSimpleMathValue(String strMath, Model modelValue) {
		strMath = strMath.trim();
		int nOperatorIndex = -1;
		nOperatorIndex = strMath.indexOf('+');
		if (nOperatorIndex == 0) {
			return getSimpleMathValue(strMath.substring(1), modelValue);
		}
		if (nOperatorIndex > 0) {// 找到+
			String strItem1 = strMath.substring(0, nOperatorIndex).trim();
			String strItem2 = strMath.substring(nOperatorIndex + 1).trim();
			long lValue1 = getSimpleMathValue(strItem1, modelValue);
			long lValue2 = getSimpleMathValue(strItem2, modelValue);
			return lValue1 + lValue2;
		}

		nOperatorIndex = strMath.indexOf('-');
		if (nOperatorIndex == 0) {
			nOperatorIndex = strMath.indexOf('-', 1);
		}
		if (nOperatorIndex > 0) {// 找到-
			String strItem1 = strMath.substring(0, nOperatorIndex).trim();
			String strItem2 = strMath.substring(nOperatorIndex + 1).trim();
			long lValue1 = getSimpleMathValue(strItem1, modelValue);
			long lValue2 = getSimpleMathValue(strItem2, modelValue);
			return lValue1 - lValue2;
		}

		nOperatorIndex = strMath.indexOf('*');
		if (nOperatorIndex == 0) {
			throw new RuntimeException("Invalid expression: " + strMath);
		}
		if (nOperatorIndex > 0) {// 找到*
			String strItem1 = strMath.substring(0, nOperatorIndex).trim();
			String strItem2 = strMath.substring(nOperatorIndex + 1).trim();
			long lValue1 = getSimpleMathValue(strItem1, modelValue);
			long lValue2 = getSimpleMathValue(strItem2, modelValue);
			return lValue1 * lValue2;
		}

		nOperatorIndex = strMath.indexOf('/');
		if (nOperatorIndex == 0) {
			throw new RuntimeException("Invalid expression: " + strMath);
		}
		if (nOperatorIndex > 0) {// 找到/
			String strItem1 = strMath.substring(0, nOperatorIndex).trim();
			String strItem2 = strMath.substring(nOperatorIndex + 1).trim();
			long lValue1 = getSimpleMathValue(strItem1, modelValue);
			long lValue2 = getSimpleMathValue(strItem2, modelValue);
			return lValue1 / lValue2;
		}
		nOperatorIndex = strMath.indexOf('%');
		if (nOperatorIndex == 0) {
			throw new RuntimeException("Invalid expression: " + strMath);
		}
		if (nOperatorIndex > 0) {// 找到%
			String strItem1 = strMath.substring(0, nOperatorIndex).trim();
			String strItem2 = strMath.substring(nOperatorIndex + 1).trim();
			long lValue1 = getSimpleMathValue(strItem1, modelValue);
			long lValue2 = getSimpleMathValue(strItem2, modelValue);
			return lValue1 % lValue2;
		}

		// 不含有运算符
		return ValueUtils.getLongValue(strMath, modelValue);
	}

	public static long getMathValue(String strMath, Model modelValue) {
		int nStartIndex = strMath.indexOf('(');
		if (nStartIndex < 0) {// 算式中没有括号
			return getSimpleMathValue(strMath, modelValue);
		}

		// 算式中有括号
		int nLength = strMath.length();
		int nIndex = nStartIndex + 1;
		while (true) {
			if (nIndex >= nLength) {
				break;
			}
			char ch = strMath.charAt(nIndex);
			if (ch == ')') {// 找到了对应的)
				String strItem = strMath.substring(nStartIndex + 1, nIndex);
				long lItemValue = getSimpleMathValue(strItem, modelValue);
				strMath = strMath.substring(0, nStartIndex) + lItemValue + strMath.substring(nIndex + 1);
				return getMathValue(strMath, modelValue);
			}
			if (ch == '(') {// 开始了新的(
				nStartIndex = nIndex;
			}
			nIndex++;
		}
		throw new RuntimeException("Invalid expression: " + strMath);
	}

	public static Model conditionToModel(String strValue1, String strOperator, String strValue2) {
		Model modelCondition = new Model();
		modelCondition.set("strValue1", strValue1);
		modelCondition.set("strOperator", strOperator);
		modelCondition.set("strValue2", strValue2);
		return modelCondition;
	}

	public static long rand(long lMinValue, long lMaxValue) {
		long lValue = random.nextLong();
		if (lValue < 0) {
			lValue = -lValue;
		}
		lValue = lMinValue + lValue % (lMaxValue + 1 - lMinValue);
		return lValue;
	}

	// public static void main(String[] args) {
	// Model modelValue = new Model();
	// modelValue.set("nNum1", 6);
	// String strMath = " ( 3 + 1 - ( 1 + {nNum1} ) ) * {nNum1}";
	//
	// long lStartTime = System.currentTimeMillis();
	// for (int i = 0; i < 100000; i++) {
	// MathExt.getMathValue(strMath, modelValue);//long lValue =
	//// System.out.println(lValue);
	// }
	// long lEndTime = System.currentTimeMillis();
	//
	// System.out.println((lEndTime - lStartTime));
	// }
}
